home *** CD-ROM | disk | FTP | other *** search
/ Aminet 15 / Aminet 15 - Nov 1996.iso / Aminet / comm / bbs / s342q16.lha / hot_help.c < prev    next >
C/C++ Source or Header  |  1996-08-29  |  9KB  |  350 lines

  1. /* Notes:
  2. In CTDL.C instead of have the doHelp() call tutorial() it should now
  3. call printHelp(filename).
  4. The code isn't commented, but you should be able to see what's happening,
  5. it is very straigtforward. If you can't decipher something drop me a
  6. note.
  7. In the HeLP files, you insert lines containing % sign followed by the
  8. topic (read: filename) of the entries you want to have displayed in
  9. the menu. Add a space and then enter text to describe it.
  10. For example, an exceprt from a help file:
  11. %FILES This menu item will display FILES.HLP
  12. %DOHELP This entry will re-show the main help file
  13. %FOO Help for idiots... :-)
  14. etc...
  15. The file nsame will be padded out to 8 characters and a letter inside
  16. square brackets will be added. The above will format into:
  17. [a] FILES     This menu item will display FILES.HLP
  18. [b] DOHELP    This entry will reshow the main help file
  19. [c] FOO       Help for idiots... :-)
  20. And then the prompt asking for a choice will appear. Every help file
  21. can contain these entries, and there is no limit to the depth that
  22. this routine can display menus.  If there are no % signs in the help
  23. file then no prompt for a choice is printed (cause no choices were
  24. displayed, right?).  I believe these are all the changes I have made,
  25. I put these routines in MISC.C...
  26. Paul Gauthier
  27. */
  28. #ifndef NORMAL_HELP
  29. #include "ctdl.h"
  30. extern CONFIG    cfg;
  31. extern logBuffer logBuf;
  32. extern char      *NoFileStr;
  33. extern char      outFlag;
  34. extern char      haveCarrier;
  35. extern char      onConsole;
  36. extern char      whichIO;
  37. extern MessageBuffer     msgBuf;
  38. /************************************************************************/
  39. /*    printHelp() does a tree structured help tutorial                  */
  40. /************************************************************************/
  41. int printHelp(char *filename)
  42.   {
  43.   FILE *file;
  44.   char nextfile[NAMESIZE + 10];
  45.   char next= TRUE;
  46.   char list[26][NAMESIZE + 10];
  47.   char plist[2];
  48.   char nlist= 0;
  49.   int toReturn, errcount;
  50.   SYS_FILE fn;
  51.   extern char *READ_TEXT;
  52.   char hit;
  53.   toReturn= TRUE;
  54.   strCpy(nextfile, filename);
  55.   while (next && toReturn != ERROR)
  56.     {
  57.     nlist= 0;
  58.     makeSysName(fn, nextfile, &cfg.homeArea);
  59.     if ((file = safeopen(fn, READ_TEXT)) == NULL)
  60.       {
  61.       mPrintf(NoFileStr, nextfile);
  62.       toReturn= ERROR;
  63.       sPrintf(msgBuf.mbtext, "Missing Help file: %s.",fn);
  64.       aideMessage(NULL,FALSE);
  65.  
  66.       }
  67.     else
  68.       {
  69.       getFileChar(file, 1);
  70.       if (outFlag != IMPERVIOUS) outFlag = OUTOK;
  71.       Output_Citadel_Message("HOTHLP",NULL,NULL,NULL);
  72.       while (getHelpNames(file, list[nlist], nlist) && nlist < 25)
  73.       nlist++;
  74.       nlist--;
  75.       if (nlist == -1)
  76.         {
  77.         next= 0;
  78.  
  79.         }
  80.       else
  81.         {
  82.         char ccx;
  83.         outFlag = OUTOK;
  84.  
  85.         Output_Citadel_Message("ENTRTN",NULL, NULL, NULL);
  86.         if (nlist == 0)
  87.           {
  88.           Output_Citadel_Message("ENTLOC",NULL, NULL, NULL);
  89.           }
  90.         else
  91.           {
  92.           plist[0] = 'a' + nlist;
  93.           plist[1] = '\0';
  94.           Output_Citadel_Message("ENTLET", (long)&plist[0],NULL, NULL);
  95.           };
  96.         next = errcount = 0;
  97.         while (onLine() && !next && (hit= toUpper( (ccx=modIn()))) != '\r' && hit != '\n')
  98.           {
  99.           if (hit - 'A' < 0 || hit - 'A' > nlist)
  100.             {
  101.             /*    mPrintf("\b \b");     */
  102.             /*    oChar('\b');
  103.             oChar(' ');
  104.             oChar('\b'); */
  105.             if (++errcount > 5 && whichIO == MODEM)
  106.             HangUp(FALSE);
  107.  
  108.             }
  109.           else
  110.             {
  111.             mPrintf("%c\n \n", hit);
  112.             strCat(list[hit - 'A'], ".HLP");
  113.             strCpy(nextfile, list[hit- 'A']);
  114.             next= TRUE;
  115.             errcount = 0;
  116.  
  117.             }
  118.  
  119.           }
  120.  
  121.         }
  122.       fclose(file);
  123.  
  124.       }
  125.  
  126.     }
  127.   return toReturn;
  128.  
  129.   }
  130. static char PB = 0;
  131. char getFileChar(FILE *file, int init)
  132.   {
  133.   static int aloop= -1;
  134.   static char line[MAXWORD];
  135.   char ret;
  136.   if (init)
  137.     {
  138.     aloop= -1;
  139.     return (char) aloop;
  140.  
  141.     }
  142.   if (PB != 0)
  143.     {
  144.     ret = PB;
  145.     PB = 0;
  146.     return ret;
  147.  
  148.     }
  149.   if (aloop == -1)
  150.     {
  151.     fgets(line, MAXWORD, file);
  152.     aloop= 0;
  153.  
  154.     }
  155.   input:
  156.   if ((ret= line[aloop++]) == 0)
  157.     {
  158.     if(!fgets(line, MAXWORD, file))
  159.     return 0;
  160.     aloop= 0;
  161.     goto input;
  162.  
  163.     }
  164.   if (outFlag == OUTSKIP) ret= 0;
  165.   return ret;
  166.  
  167.   }
  168. #define INT_PTR         0
  169. #define CHAR_PTR        1
  170. #define FUNC_PTR        2
  171. static struct
  172.   {
  173.   char *ourname;
  174.   char type;
  175.   union
  176.     {
  177.     UNS_16 *where;
  178.     char   *addr;
  179.     void   (*funcptr)(char *);
  180.  
  181.     }
  182.   goo;
  183.  
  184.   }
  185. VarNames[] =
  186.   {
  187.     {    "nodetitle",  INT_PTR, &cfg.nodeTitle     },
  188.     {    "nodename",   INT_PTR, &cfg.nodeName     },
  189.     {    "nodedomain", INT_PTR, &cfg.nodeDomain     },
  190.     {    "nodeid",     INT_PTR, &cfg.nodeId     },
  191.     {    "baseroom",   INT_PTR, &cfg.bRoom     },
  192.     {    "mainfloor",  INT_PTR, &cfg.MainFloor     },
  193.     {    "variantname",CHAR_PTR,(unsigned short *)VARIANT_NAME     },
  194.     {    "sysopname",  CHAR_PTR,(unsigned short *)cfg.SysopName     },
  195.     {    "ulprotocols",FUNC_PTR,(unsigned short *)UpProtsEnglish     },
  196.     {    "dlprotocols",FUNC_PTR,(unsigned short *)DownProtsEnglish     },
  197.     {    "doorlist",   FUNC_PTR,(unsigned short *)DoorHelpListing     },
  198.  
  199.   };
  200. getHelpNames(FILE *file, char *name, char count)
  201.   {
  202.   char work[20], c, *t;
  203.   char buf[MAXWORD + 1];
  204.   int loop= 0, i;
  205.   extern MessageBuffer msgBuf;
  206.   SYS_FILE fn;
  207.   round:
  208.   while((buf[loop]= getFileChar(file, 0)) != '%' && buf[loop] && loop < MAXWORD-1)
  209.     {
  210.     if (buf[loop] == '^')
  211.       {
  212.       if (loop > MAXWORD - 50)
  213.         {
  214.         buf[loop] = 0;
  215.         loop= 0;
  216.         mPrintf("%s", buf);
  217.  
  218.         }
  219.       i = 0;
  220.       while(isalpha(work[i] = getFileChar(file, 0)) &&
  221.       i < (sizeof work) - 1)
  222.       i++;
  223.       c = work[i];
  224.       work[i] = 0;
  225.       /* printf("\nSearching on '%s'.\n", work); */
  226.       for (i = 0; i < NumElems(VarNames); i++)
  227.       if (strCmpU(VarNames[i].ourname, work) == SAMESTRING)
  228.       break;
  229.       if (i < NumElems(VarNames))
  230.         {
  231.         switch (VarNames[i].type)
  232.           {
  233.           case INT_PTR:
  234.           t = cfg.codeBuf + *VarNames[i].goo.where;
  235.           break;
  236.           case CHAR_PTR:
  237.           t = VarNames[i].goo.addr;
  238.           break;
  239.           case FUNC_PTR:
  240.           t = msgBuf.mbtext;
  241.           (*VarNames[i].goo.funcptr)(msgBuf.mbtext);
  242.           if (strLen(t) + loop > sizeof buf - 1)
  243.             {
  244.             buf[loop] = 0;
  245.             mPrintf("%s", buf);
  246.             loop = 0;
  247.             if (strLen(msgBuf.mbtext) > sizeof buf)
  248.               {
  249.               mPrintf("%s", msgBuf.mbtext);
  250.               msgBuf.mbtext[0] = 0;
  251.  
  252.               }
  253.  
  254.             }
  255.           break;
  256.  
  257.           }
  258.         buf[loop] = 0;
  259.         strcat(buf, t);
  260.         loop = strLen(buf);
  261.  
  262.         }
  263.       else
  264.         {
  265.         for (loop++, i = 0; work[i] && loop < MAXWORD - 1;
  266.         loop++, i++)
  267.         buf[loop] = work[i];
  268.  
  269.         }
  270.       buf[loop++] = c;
  271.  
  272.       }
  273.     /*
  274.     * prevent words from being cut in half -- occasionally screws up
  275.     * formatting if we don't do this in long help files.
  276.     */
  277.     else if (buf[loop] == ' ' && loop > MAXWORD - 12)
  278.       {
  279.       break;
  280.  
  281.       }
  282.     else
  283.     loop++;
  284.  
  285.     }
  286.   if (!buf[loop])
  287.     {
  288.     mPrintf("%s", buf);
  289.     return FALSE;
  290.  
  291.     }
  292.   /*     if(loop == MAXWORD-1) */
  293.   if (buf[loop] != '%')
  294.     {
  295.     buf[loop+1]= 0;
  296.     loop= 0;
  297.     mPrintf("%s", buf);
  298.     goto round;
  299.  
  300.     }
  301.   buf[loop]= 0;
  302.   outFlag = OUTOK;
  303.   mPrintf("%s", buf);
  304.   loop= 0;
  305.   while((name[loop]= getFileChar(file, 0)) != ' ' && name[loop] && loop <= 7)
  306.   loop++;
  307.   name[loop]= 0;
  308.   sPrintf(work, "%s.hlp", name);
  309.   makeSysName(fn, work, &cfg.homeArea);
  310.   if (access(fn, 0) != 0)
  311.     {
  312.     /*
  313.     * don't show the file name or its comment -- so the unwary won't
  314.     * stumble into nothingness.
  315.     */
  316.     while ((c = getFileChar(file, 0)) != 0 && c != '\n')
  317.     ;
  318.     loop= 0;
  319.     buf[0]= 0;
  320.     /*
  321.     * This bizarre little if with a pushback is the result of noticing
  322.     * when help files are missing, the help file trying to find them
  323.     * will pile up the leading spaces which characterize most help files
  324.     * in the " %MYHELP" stuff.  This makes the listing of help files to
  325.     * jump to "lumpy."  The if right here takes care of that by peeking
  326.     * ahead and killing a leading space if it's there.  This is obviously
  327.     * not a perfect solution, but hopefully the imperfections will rarely
  328.     * show up.
  329.     */
  330.     if ((c = getFileChar(file, 0)) != ' ')
  331.     PB = c;
  332.     goto round; /* eeeeeeeyyyyyyyuuuuuuuuuucccccccckkkk! */
  333.  
  334.     }
  335.   mPrintf("[%c] %-8s  ", 'a' + count, name);
  336.   return TRUE;
  337.  
  338.   }
  339. /**************************** EOS (end of source) ****************************/
  340. #else
  341. /************************************************************************/
  342. /*    printHelp() does a tree structured help tutorial                  */
  343. /************************************************************************/
  344. int printHelp(char *filename)
  345.   {
  346.   tutorial(filename, 1);
  347.  
  348.   }
  349. #endif
  350.